package com.wfs.myapp.remote.wx;

import com.alibaba.fastjson.JSONObject;
import com.wfs.myapp.config.MessageSendConfig;
import com.wfs.myapp.entity.domain.User;
import com.wfs.myapp.remote.wx.dto.SendMessageDto;
import com.wfs.myapp.remote.wx.vo.OpenIdVo;
import com.wfs.myapp.remote.wx.vo.SendMessageVo;
import com.wfs.myapp.remote.wx.vo.WxAccessTokenVo;
import com.wfs.myapp.utils.HttpUtil;
import com.wfs.myapp.utils.SHA1Utils;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import java.io.UnsupportedEncodingException;
import java.util.HashMap;
import java.util.Map;
import java.util.Objects;

@Service
@Slf4j
public class WxRemoteService {

    private final String OPEN_ID_URL = "https://api.weixin.qq.com/sns/jscode2session";
    private final String ACCESS_TOKEN_URL = "https://api.weixin.qq.com/cgi-bin/token";
    private final String SEND_MESSAGE_URL = "https://api.weixin.qq.com/cgi-bin/message/subscribe/send?access_token=";
    private final String GENERATE_QR_URL = "https://api.weixin.qq.com/wxa/getwxacodeunlimit?access_token=";
    private final String SCAN_QR_CODE_URL = "https://api.weixin.qq.com/cv/img/qrcode?access_token=";


    @Value("${app.appid}")
    private String appid;

    @Value("${app.secret}")
    private String appSecret;

    @Autowired
    private HttpUtil httpClient;

    public OpenIdVo getOpenId(String code) {
        String url = OPEN_ID_URL + "?appid=" + appid + "&secret=" + appSecret + "&js_code=" + code + "&grant_type=authorization_code";
        String s = httpClient.get(url);
        log.info("wx get openid resp: {}", s);
        OpenIdVo openIdVo = JSONObject.parseObject(s, OpenIdVo.class);
        if (Objects.nonNull(openIdVo.getErrcode()) && !openIdVo.getErrcode().equals(0)) {
            throw new RuntimeException(openIdVo.getErrmsg());
        }
        return openIdVo;
    }

    public WxAccessTokenVo getAccessToken() {
        String url = ACCESS_TOKEN_URL + "?appid=" + appid + "&secret=" + appSecret + "&grant_type=client_credential";
        String s = httpClient.get(url);
        log.info("get access token resp: {}", s);
        WxAccessTokenVo accessTokenVo = JSONObject.parseObject(s, WxAccessTokenVo.class);
        return accessTokenVo;
    }

    public String msgSend(String signature, String echostr, String timestamp, String nonce) {
        String sourceStr = timestamp + nonce + MessageSendConfig.TOKEN;
        String sha1Signature = SHA1Utils.SHA1Example(sourceStr);
        if (signature.equals(sha1Signature)) {
            return echostr;
        }
        log.error("smgSend error, sha1 signature is {}", sha1Signature);
        return "error";
    }

    public SendMessageVo sendMessage(String openid, String bookName, String deadline, String remainDay, String remark) {
        String url = SEND_MESSAGE_URL + this.getAccessToken().getAccess_token();
        // build push data
        SendMessageDto.BkReturnMsgTemplateDto bkReturnMsgTemplateDto = new SendMessageDto.BkReturnMsgTemplateDto();
        bkReturnMsgTemplateDto.setThing3(new SendMessageDto.ValueDto(bookName));
        bkReturnMsgTemplateDto.setDate1(new SendMessageDto.ValueDto(deadline));
        bkReturnMsgTemplateDto.setShort_thing5(new SendMessageDto.ValueDto(remainDay));
        bkReturnMsgTemplateDto.setThing4(new SendMessageDto.ValueDto(remark));
        // push
        SendMessageDto<SendMessageDto.BkReturnMsgTemplateDto> sendMessageDto = new SendMessageDto();
        sendMessageDto.setTemplate_id(MessageSendConfig.RETURN_MSG_TEMPLATE_ID);
        sendMessageDto.setTouser(openid);
        sendMessageDto.setData(bkReturnMsgTemplateDto);
        sendMessageDto.setMiniprogram_state("formal");
        sendMessageDto.setLang("zh_CN");
        String sendMessageRes = httpClient.post(url, sendMessageDto);
        log.info("sendMessageVoRes str: {}", sendMessageRes);
        SendMessageVo sendMessageVo = JSONObject.parseObject(sendMessageRes, SendMessageVo.class);
        log.info("sendMessageVo: {}", sendMessageVo);
        return sendMessageVo;
    }

    public SendMessageVo sendMessageByBirthdayRemind(User user, String name, String birthday, String remark) {
        String url = SEND_MESSAGE_URL + this.getAccessToken().getAccess_token();
        // build push data
//        SendMessageDto.BkBirthdayRemindMsgTemplateDto bkBirthdayRemindMsgTemplateDto = new SendMessageDto.BkBirthdayRemindMsgTemplateDto();
//        bkBirthdayRemindMsgTemplateDto.setThing2(new SendMessageDto.ValueDto(name));
//        bkBirthdayRemindMsgTemplateDto.setTime1(new SendMessageDto.ValueDto(birthday));
//        bkBirthdayRemindMsgTemplateDto.setThing3(new SendMessageDto.ValueDto(remark));

        SendMessageDto.BkWeChatPushMsgTemplateDto weChatPushMsgTemplateDto = new SendMessageDto.BkWeChatPushMsgTemplateDto();
        weChatPushMsgTemplateDto.setThing5(new SendMessageDto.ValueDto(name));
        weChatPushMsgTemplateDto.setThing3(new SendMessageDto.ValueDto(remark));
        weChatPushMsgTemplateDto.setName1(new SendMessageDto.ValueDto("" + user.getNickname()));
        weChatPushMsgTemplateDto.setDate2(new SendMessageDto.ValueDto(birthday));

        // push
        SendMessageDto<SendMessageDto.BkWeChatPushMsgTemplateDto> sendMessageDto = new SendMessageDto();
        sendMessageDto.setTemplate_id(MessageSendConfig.WECHAT_PUSH_MSG_TEMPLATE_ID);
        sendMessageDto.setTouser(user.getOpenid());
        sendMessageDto.setData(weChatPushMsgTemplateDto);
        sendMessageDto.setMiniprogram_state("formal");
        sendMessageDto.setLang("zh_CN");
        String sendMessageRes = httpClient.post(url, sendMessageDto);
        log.info("sendMessageVoRes str: {}", sendMessageRes);
        SendMessageVo sendMessageVo = JSONObject.parseObject(sendMessageRes, SendMessageVo.class);
        log.info("sendMessageVo: {}", sendMessageVo);
        return sendMessageVo;
    }

    public byte[] getQrCode(String page, String scene) {
        String url = GENERATE_QR_URL + this.getAccessToken().getAccess_token();
        JSONObject params = new JSONObject();
        params.put("env_version", "release"); // 默认就是生产模式，trial开发模式
        params.put("page", page);
        params.put("scene", scene);
        params.put("check_path", false);
        Map<String,String> header = new HashMap<>();
        header.put("Content-Type", "application/json");
        byte[] body = httpClient.postBody(url, header, params);
        String result;
        // 转base64
//        result = Constant.IMAGE_BASE64_PRE + new String(Base64.getEncoder().encode(body));
        return body;
    }

    public String scanQrCode() throws UnsupportedEncodingException {
        String url = SCAN_QR_CODE_URL + this.getAccessToken().getAccess_token();
//                + "&img_url=" + URLEncoder.encode("https://lexiaoli.top:8091/file/image/book?imageName=book_avatar_4.png", "UTF-8");
        JSONObject params = new JSONObject();
//        params.put("img_url", URLEncoder.encode("https://lexiaoli.top:8091/file/image/book?imageName=book_avatar_4.png", "UTF-8")); // 默认就是生产模式，trial开发模式
        params.put("img_url", "@C:\\Users\\wang\\Desktop\\book.jpeg"); // 默认就是生产模式，trial开发模式
//        params.put("page", page);
//        params.put("scene", scene);
//        params.put("check_path", false);
        Map<String,String> header = new HashMap<>();
        header.put("Content-Type", "multipart/form-data");
        header.put("meta-data", "form-data");
        String result = httpClient.post(url, header, params);
        return result;
    }


}
